import React, { useState, useRef } from 'react';
import Modal from '../../Modal';
import EditableText from '../../EditableText';
import { AiPrompts, MacroFunction, MacroScope, MacroFunctionParameter, AiPromptKey, GameData, ChatMessage, AiPromptsChatHistory, GameSettings } from '../../../types';
import { TrashIcon, PencilIcon, QuestionMarkCircleIcon, ArrowDownTrayIcon, SparklesIcon } from '../../icons';
import { v4 as uuidv4 } from 'uuid';
import SinglePromptTuningModal from './SinglePromptTuningModal';
import { generateInitialAiPrompts, getModelAndChannel } from '../../../services/apiService';
import LoadingSpinner from '../../LoadingSpinner';


interface AiConfigModalProps {
    isOpen: boolean;
    onClose: () => void;
    gameData: GameData;
    settings: GameSettings;
    editablePrompts: AiPrompts;
    editableMacros: MacroFunction[];
    editableChatHistory: AiPromptsChatHistory;
    setEditablePrompts: React.Dispatch<React.SetStateAction<AiPrompts>>;
    setEditableMacros: React.Dispatch<React.SetStateAction<MacroFunction[]>>;
    setEditableChatHistory: React.Dispatch<React.SetStateAction<AiPromptsChatHistory>>;
    onSave: () => void;
    onShowHelp: (content: { title: string; content: any }) => void;
    nativeFunctionsDoc: any;
    macroTutorial: any;
    showToast: (message: string, type?: 'success' | 'error') => void;
    isGuideActive?: boolean;
    onGuideAdvance?: () => void;
}

const ArrowUpTrayIcon: React.FC<React.SVGProps<SVGSVGElement>> = (props) => (
    <svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" strokeWidth={1.5} stroke="currentColor" {...props}>
      <path strokeLinecap="round" strokeLinejoin="round" d="M3 16.5v2.25A2.25 2.25 0 005.25 21h13.5A2.25 2.25 0 0021 18.75V16.5m-13.5-9L12 3m0 0l4.5 4.5M12 3v13.5" />
    </svg>
);

const scopeOptions: { value: MacroScope; label: string }[] = [
    { value: MacroScope.Planning, label: '规划' },
    { value: MacroScope.Narrative, label: '叙事' },
    { value: MacroScope.Status, label: '状态' },
    { value: MacroScope.Tool, label: '工具' },
];

const AiConfigModal: React.FC<AiConfigModalProps> = ({
    isOpen,
    onClose,
    gameData,
    settings,
    editablePrompts,
    editableMacros,
    editableChatHistory,
    setEditablePrompts,
    setEditableMacros,
    setEditableChatHistory,
    onSave,
    onShowHelp,
    nativeFunctionsDoc,
    macroTutorial,
    showToast,
    isGuideActive,
    onGuideAdvance,
}) => {
    const [tab, setTab] = useState<'prompts' | 'macros' | 'system'>('prompts');
    const [isMacroEditorOpen, setIsMacroEditorOpen] = useState(false);
    const [editingMacro, setEditingMacro] = useState<MacroFunction | null>(null);
    const [currentMacroForm, setCurrentMacroForm] = useState<Partial<MacroFunction>>({});
    const macroFileInputRef = useRef<HTMLInputElement>(null);
    const [isTuningModalOpen, setIsTuningModalOpen] = useState(false);
    const [tuningPromptKey, setTuningPromptKey] = useState<AiPromptKey | null>(null);
    const [isGenerating, setIsGenerating] = useState(false);
    const [generationProgress, setGenerationProgress] = useState("");
    
    const isInitialSetup = !editablePrompts.scenarioGenerationPrompt;

    const handleGeneratePrompts = async () => {
        const { model, channel } = getModelAndChannel(settings, settings.defaultTextModelId);
        if (!model || !channel) {
            showToast("请先在全局设置中配置一个默认文本模型。", "error");
            return;
        }
        setIsGenerating(true);
        setGenerationProgress("开始生成...");
        try {
            const onProgress = (message: string) => setGenerationProgress(message);
            const newCorePrompts = await generateInitialAiPrompts(gameData.rulebook, channel, model, settings.corsProxyUrl, settings.requestTimeout, onProgress);
            setEditablePrompts(prev => ({ ...prev, ...newCorePrompts }));
            showToast("初始提示词生成成功！", "success");
            if (isGuideActive && onGuideAdvance) {
                onGuideAdvance();
            }
        } catch (error) {
            showToast(`生成提示词失败: ${error instanceof Error ? error.message : "未知错误"}`, "error");
        } finally {
            setIsGenerating(false);
            setGenerationProgress("");
        }
    };

    const handlePromptEdit = (promptKey: keyof AiPrompts, value: string) => {
        setEditablePrompts(prev => ({ ...prev, [promptKey]: value }));
    };

    const handleTuningModalOpen = (promptKey: AiPromptKey) => {
        setTuningPromptKey(promptKey);
        setIsTuningModalOpen(true);
    };
    
    const handlePromptTuningFinalized = (promptKey: AiPromptKey, newPrompt: string, newHistory: ChatMessage[]) => {
        handlePromptEdit(promptKey, newPrompt);
        setEditableChatHistory(prev => ({...prev, [promptKey]: newHistory}));
        setIsTuningModalOpen(false);
        setTuningPromptKey(null);
    };

    const openNewMacroModal = () => {
        setEditingMacro(null);
        setCurrentMacroForm({ name: '', description: '', parameters: [], isNative: false, isEnabled: true, logic: '', outputTemplate: '', scopes: [MacroScope.Planning] });
        setIsMacroEditorOpen(true);
    };

    const openEditMacroModal = (macro: MacroFunction) => {
        setEditingMacro(macro);
        setCurrentMacroForm(JSON.parse(JSON.stringify(macro))); // Deep copy
        setIsMacroEditorOpen(true);
    };
    
    const handleMacroScopeChange = (scope: MacroScope, checked: boolean) => {
        setCurrentMacroForm(prev => {
            const currentScopes = prev.scopes || [];
            const newScopes = checked
                ? [...currentScopes, scope]
                : currentScopes.filter(s => s !== scope);
            return { ...prev, scopes: newScopes };
        });
    };

    const handleSaveMacro = () => {
        if (!currentMacroForm.name || !currentMacroForm.logic || !currentMacroForm.outputTemplate) {
            showToast("宏函数的名称、逻辑和输出模板不能为空。", "error");
            return;
        }
        if (!currentMacroForm.scopes || currentMacroForm.scopes.length === 0) {
            showToast("必须为宏函数至少选择一个作用域。", "error");
            return;
        }
        const newMacros = [...editableMacros];
        if (editingMacro) {
            const index = newMacros.findIndex(m => m.id === editingMacro.id);
            if (index > -1) newMacros[index] = { ...editingMacro, ...currentMacroForm } as MacroFunction;
        } else {
            newMacros.push({ id: uuidv4(), ...currentMacroForm } as MacroFunction);
        }
        setEditableMacros(newMacros);
        setIsMacroEditorOpen(false);
    };

    const handleDeleteMacro = (macroId: string) => {
        setEditableMacros(prev => prev.filter(m => m.id !== macroId));
    };
    
    const handleExportMacros = () => {
        if (!editableMacros || editableMacros.length === 0) {
            showToast("没有宏函数可导出。", "error");
            return;
        }
        const filename = `jrpg_macros_${new Date().toISOString().slice(0, 10)}.json`;
        const jsonStr = JSON.stringify(editableMacros, null, 2);
        const blob = new Blob([jsonStr], { type: "application/json" });
        const url = URL.createObjectURL(blob);
        const a = document.createElement("a");
        a.href = url;
        a.download = filename;
        document.body.appendChild(a);
        a.click();
        document.body.removeChild(a);
        URL.revokeObjectURL(url);
        showToast("宏函数配置已导出!", "success");
    };

    const triggerImportMacros = () => {
        macroFileInputRef.current?.click();
    };

    const handleImportMacrosFileChange = async (event: React.ChangeEvent<HTMLInputElement>) => {
        const file = event.target.files?.[0];
        if (file) {
            const reader = new FileReader();
            reader.onload = (e) => {
                try {
                    const text = e.target?.result as string;
                    const importedMacros = JSON.parse(text);
                    if (Array.isArray(importedMacros)) {
                        const isValid = importedMacros.every((m: any) =>
                            typeof m === 'object' && m !== null &&
                            'id' in m && 'name' in m && 'description' in m &&
                            'parameters' in m && 'isNative' in m && 'isEnabled' in m &&
                            'logic' in m && 'outputTemplate' in m &&
                            ('scopes' in m && Array.isArray(m.scopes)) // Also check for scopes
                        );

                        if (isValid) {
                            setEditableMacros(importedMacros);
                            showToast("宏函数已成功导入并替换当前配置!", "success");
                        } else {
                            showToast("导入失败: 文件内容格式不正确或缺少必要字段 (包括scopes和isEnabled)。", "error");
                        }
                    } else {
                        showToast("导入失败: 文件应包含一个宏函数数组。", "error");
                    }
                } catch (error) {
                    showToast(`导入失败: ${error instanceof Error ? error.message : "无法解析文件。"}`, "error");
                } finally {
                    if (macroFileInputRef.current) {
                        macroFileInputRef.current.value = "";
                    }
                }
            };
            reader.readAsText(file);
        }
    };

    const renderPromptField = (promptKey: AiPromptKey, label: string, description?: string) => (
        <div>
            <div className="flex justify-between items-center mb-1">
                <label className="block text-sm font-medium text-gray-300">{label}</label>
                <button 
                    onClick={() => handleTuningModalOpen(promptKey)}
                    className="flex items-center gap-1 text-xs px-2 py-1 bg-sky-600 hover:bg-sky-700 rounded-md text-white transition-colors"
                    title="与AI深入讨论优化"
                >
                    <SparklesIcon className="w-4 h-4" />
                    <span>讨论优化</span>
                </button>
            </div>
            <EditableText isTextArea initialValue={editablePrompts[promptKey] || ''} onSave={(val) => handlePromptEdit(promptKey, val)} className="w-full" textClassName="text-sm p-2 border border-gray-600 rounded min-h-[80px] bg-gray-700 hover:bg-gray-600" inputClassName="bg-gray-600 text-gray-100 p-2 rounded w-full min-h-[80px] text-sm" />
            {description && <p className="text-xs text-gray-400 mt-1">{description}</p>}
        </div>
    );

    return (
        <>
            <Modal
                isOpen={isOpen}
                onClose={onClose}
                title="编辑AI配置"
                footer={
                    <div className="flex justify-end space-x-2">
                        <button onClick={onClose} className="px-4 py-2 bg-gray-600 hover:bg-gray-700 text-white rounded-md">取消</button>
                        <button data-guide-id="save-ai-config-btn" onClick={onSave} className="px-4 py-2 bg-blue-600 hover:bg-blue-700 text-white rounded-md">保存配置</button>
                    </div>
                }
            >
                <div className="space-y-4">
                     {isInitialSetup && (
                        <div className="p-4 bg-blue-900/50 border border-blue-700 rounded-lg text-center">
                            {isGenerating ? (
                                <LoadingSpinner text={generationProgress} />
                            ) : (
                                <button
                                    data-guide-id="generate-prompts-btn"
                                    onClick={handleGeneratePrompts}
                                    className="w-full px-4 py-3 bg-green-600 hover:bg-green-700 text-white font-semibold rounded-md shadow-sm transition-colors text-base flex items-center justify-center gap-2"
                                >
                                    <SparklesIcon className="w-5 h-5" />
                                    让AI根据规则书生成初始提示词
                                </button>
                            )}
                            <p className="text-xs text-gray-400 mt-2">这是开始游戏的第一步。您也可以选择手动填写下方的提示词。</p>
                        </div>
                    )}
                    <div className="flex border-b border-gray-700">
                        <button className={`px-4 py-2 text-sm font-medium ${tab === 'prompts' ? 'border-b-2 border-blue-500 text-white' : 'text-gray-400 hover:text-white'}`} onClick={() => setTab('prompts')}>核心提示词</button>
                        <button className={`px-4 py-2 text-sm font-medium ${tab === 'macros' ? 'border-b-2 border-blue-500 text-white' : 'text-gray-400 hover:text-white'}`} onClick={() => setTab('macros')}>宏函数 (测试中)</button>
                        <button className={`px-4 py-2 text-sm font-medium ${tab === 'system' ? 'border-b-2 border-blue-500 text-white' : 'text-gray-400 hover:text-white'}`} onClick={() => setTab('system')}>系统指令 (测试中)</button>
                    </div>
                    {tab === 'prompts' && (
                        <div className="space-y-4">
                            {renderPromptField('scenarioGenerationPrompt', '场景生成提示 (通用)')}
                            {renderPromptField('functionCallingNarrativePrompt', '函数调用模式叙事原则 (可选)', '如果留空，函数调用模式将使用上面的“场景生成提示”。如果填写，则会优先使用此处的原则。')}
                            {renderPromptField('statusPanelPrompt', '状态面板提示')}
                            {renderPromptField('keyInfoExtractionPrompt', '关键信息提取提示')}
                        </div>
                    )}
                     {tab === 'system' && (
                        <div className="space-y-4">
                            {renderPromptField('calculationHelperSystemPrompt', '规划AI系统指令 (计算助手)')}
                            {renderPromptField('narrativeWithCalcsSystemPrompt', '叙事AI系统指令 (带计算结果)')}
                            {renderPromptField('hybridStructuredDataSystemPrompt', '数据AI系统指令 (混合模式)')}
                            {renderPromptField('toolCallingSystemPrompt', '全能AI系统指令 (函数调用模式)')}
                        </div>
                    )}
                    {tab === 'macros' && (
                        <div className="space-y-3">
                            <div className="flex flex-col sm:flex-row gap-2 mb-3">
                                <button onClick={() => onShowHelp({ title: '原生函数文档', content: nativeFunctionsDoc })} className="flex-1 text-center text-sm px-3 py-2 bg-sky-600 hover:bg-sky-700 rounded-md flex items-center justify-center gap-2">
                                    <QuestionMarkCircleIcon className="w-5 h-5" /> 查看原生函数文档
                                </button>
                                <button onClick={() => onShowHelp({ title: '宏函数编写教程', content: macroTutorial })} className="flex-1 text-center text-sm px-3 py-2 bg-teal-600 hover:bg-teal-700 rounded-md flex items-center justify-center gap-2">
                                    <QuestionMarkCircleIcon className="w-5 h-5" /> 宏函数编写教程
                                </button>
                            </div>
                            {editableMacros.map(macro => (
                                <div key={macro.id} className="p-3 bg-gray-700 rounded-lg">
                                    <div className="flex justify-between items-start">
                                        <div className='flex-grow'>
                                            <p className="font-medium text-gray-100">{macro.name} {macro.isNative && <span className="text-xs ml-2 px-1.5 py-0.5 bg-sky-600 rounded-full">原生</span>}</p>
                                            <p className="text-xs text-gray-400 mt-1">{macro.description}</p>
                                            <div className="mt-2 flex flex-wrap gap-2">
                                                {macro.scopes?.map(scope => (
                                                    <span key={scope} className="text-xs px-1.5 py-0.5 bg-gray-600 text-gray-300 rounded-full">{scopeOptions.find(o=>o.value === scope)?.label || scope}</span>
                                                ))}
                                            </div>
                                        </div>
                                        <div className="flex items-center space-x-2">
                                            <label htmlFor={`macro-toggle-${macro.id}`} className="flex items-center cursor-pointer">
                                                <div className="relative">
                                                    <input
                                                        type="checkbox"
                                                        id={`macro-toggle-${macro.id}`}
                                                        className="sr-only"
                                                        checked={macro.isEnabled}
                                                        onChange={(e) => {
                                                            const newMacros = editableMacros.map(m => m.id === macro.id ? {...m, isEnabled: e.target.checked} : m);
                                                            setEditableMacros(newMacros);
                                                        }}
                                                    />
                                                    <div className={`block ${macro.isEnabled ? 'bg-blue-600' : 'bg-gray-600'} w-10 h-6 rounded-full`}></div>
                                                    <div className={`dot absolute left-1 top-1 bg-white w-4 h-4 rounded-full transition-transform ${macro.isEnabled ? 'transform translate-x-4' : ''}`}></div>
                                                </div>
                                            </label>
                                            <button onClick={() => openEditMacroModal(macro)} className="p-1.5 text-yellow-400 hover:text-yellow-300"><PencilIcon className="w-5 h-5" /></button>
                                            <button onClick={() => handleDeleteMacro(macro.id)} className="p-1.5 text-red-500 hover:text-red-400"><TrashIcon className="w-5 h-5" /></button>
                                        </div>
                                    </div>
                                </div>
                            ))}
                            <div className="flex flex-col sm:flex-row gap-2 mt-4">
                                <button onClick={openNewMacroModal} className="flex-1 text-center text-sm px-3 py-2 bg-green-600 hover:bg-green-700 rounded-md text-white font-semibold shadow-sm transition-colors">添加宏函数</button>
                                <button onClick={triggerImportMacros} className="flex-1 text-center text-sm px-3 py-2 bg-sky-600 hover:bg-sky-700 rounded-md text-white font-semibold shadow-sm transition-colors flex items-center justify-center gap-2"><ArrowUpTrayIcon className="w-5 h-5" /> 导入宏</button>
                                <button onClick={handleExportMacros} className="flex-1 text-center text-sm px-3 py-2 bg-indigo-600 hover:bg-indigo-700 rounded-md text-white font-semibold shadow-sm transition-colors flex items-center justify-center gap-2"><ArrowDownTrayIcon className="w-5 h-5" /> 导出宏</button>
                            </div>
                            <input type="file" accept=".json" ref={macroFileInputRef} onChange={handleImportMacrosFileChange} className="hidden" />
                        </div>
                    )}
                </div>
            </Modal>
            {isTuningModalOpen && tuningPromptKey && (
                <SinglePromptTuningModal
                    isOpen={isTuningModalOpen}
                    onClose={() => setIsTuningModalOpen(false)}
                    promptKey={tuningPromptKey}
                    initialPromptText={editablePrompts[tuningPromptKey] || ''}
                    initialChatHistory={editableChatHistory[tuningPromptKey] || []}
                    gameData={gameData}
                    settings={settings}
                    showToast={showToast}
                    onFinalize={handlePromptTuningFinalized}
                />
            )}
            <Modal isOpen={isMacroEditorOpen} onClose={() => setIsMacroEditorOpen(false)} title={editingMacro ? "编辑宏函数" : "添加宏函数"}>
                <div className="space-y-4 text-sm">
                    <div><label className="block font-medium text-gray-300 mb-1">函数名称</label><input type="text" value={currentMacroForm.name || ''} onChange={e => setCurrentMacroForm(p => ({ ...p, name: e.target.value }))} className="w-full p-2 bg-gray-700 rounded" placeholder="例如: damage" /></div>
                    <div><label className="block font-medium text-gray-300 mb-1">函数描述 (给AI看)</label><textarea value={currentMacroForm.description || ''} onChange={e => setCurrentMacroForm(p => ({ ...p, description: e.target.value }))} className="w-full p-2 bg-gray-700 rounded" rows={2} placeholder="例如: 计算一次攻击造成的伤害。" /></div>
                    <div>
                        <label className="block font-medium text-gray-300 mb-1">参数</label>
                        <div className="space-y-2">
                            {currentMacroForm.parameters?.map((param, index) => (
                                <div key={index} className="grid grid-cols-1 md:grid-cols-2 gap-2 items-center">
                                    <input type="text" placeholder="参数名" value={param.name} onChange={e => { const newParams = [...currentMacroForm.parameters!]; newParams[index].name = e.target.value; setCurrentMacroForm(p => ({ ...p, parameters: newParams })); }} className="w-full p-2 bg-gray-600 rounded" />
                                    <div className="flex items-center gap-2">
                                        <input type="text" placeholder="参数描述" value={param.description} onChange={e => { const newParams = [...currentMacroForm.parameters!]; newParams[index].description = e.target.value; setCurrentMacroForm(p => ({ ...p, parameters: newParams })); }} className="w-full p-2 bg-gray-600 rounded" />
                                        <button onClick={() => { const newParams = [...currentMacroForm.parameters!]; newParams.splice(index, 1); setCurrentMacroForm(p => ({ ...p, parameters: newParams })); }} className="p-1.5 text-red-500 hover:text-red-400"><TrashIcon className="w-4 h-4" /></button>
                                    </div>
                                </div>
                            ))}
                        </div>
                        <button onClick={() => { const newParams = [...(currentMacroForm.parameters || [])]; newParams.push({ name: '', description: ''}); setCurrentMacroForm(p => ({ ...p, parameters: newParams })); }} className="mt-2 text-xs px-2 py-1 bg-gray-600 hover:bg-gray-500 rounded">添加参数</button>
                    </div>
                     <div>
                        <label className="block font-medium text-gray-300 mb-1">作用域 (Scope)</label>
                        <div className="flex flex-wrap gap-x-4 gap-y-2">
                            {scopeOptions.map(opt => (
                                <label key={opt.value} className="flex items-center space-x-2 text-gray-200">
                                    <input
                                        type="checkbox"
                                        checked={currentMacroForm.scopes?.includes(opt.value) ?? false}
                                        onChange={(e) => handleMacroScopeChange(opt.value, e.target.checked)}
                                        className="w-4 h-4 rounded bg-gray-600 border-gray-500 text-blue-500 focus:ring-blue-600"
                                    />
                                    <span>{opt.label}</span>
                                </label>
                            ))}
                        </div>
                    </div>
                    <div><label className="block font-medium text-gray-300 mb-1">逻辑 (Javascript代码)</label><textarea value={currentMacroForm.logic || ''} onChange={e => setCurrentMacroForm(p => ({ ...p, logic: e.target.value }))} className="w-full p-2 bg-gray-900 text-cyan-300 font-mono rounded" rows={4} placeholder="return args.power * 2;" disabled={currentMacroForm.isNative} />{currentMacroForm.isNative && <p className="text-xs text-sky-400 mt-1">原生函数的逻辑不可编辑。</p>}</div>
                    <div><label className="block font-medium text-gray-300 mb-1">输出模板</label><textarea value={currentMacroForm.outputTemplate || ''} onChange={e => setCurrentMacroForm(p => ({ ...p, outputTemplate: e.target.value }))} className="w-full p-2 bg-gray-700 rounded" rows={2} placeholder="例如: ${attacker} 对 ${target} 造成了 ${result} 点伤害。" /></div>
                     <div className="flex items-center space-x-2 pt-2">
                        <input
                            type="checkbox"
                            id="macro-enabled-checkbox"
                            checked={currentMacroForm.isEnabled ?? true}
                            onChange={(e) => setCurrentMacroForm(p => ({ ...p, isEnabled: e.target.checked }))}
                            className="w-4 h-4 rounded bg-gray-600 border-gray-500 text-blue-500 focus:ring-blue-600"
                        />
                        <label htmlFor="macro-enabled-checkbox" className="font-medium text-gray-300">启用此宏函数</label>
                    </div>
                    <div className="flex justify-end space-x-3 pt-4">
                        <button onClick={() => setIsMacroEditorOpen(false)} className="px-4 py-2 bg-gray-600 hover:bg-gray-700 rounded text-white">取消</button>
                        <button onClick={handleSaveMacro} className="px-4 py-2 bg-blue-600 hover:bg-blue-700 rounded text-white">保存</button>
                    </div>
                </div>
            </Modal>
        </>
    );
};

export default AiConfigModal;